package com.starview.star.compiler.format.rules;

import com.starview.platform.data.IArray;
import com.starview.platform.data.type.Location;
import com.starview.star.compiler.ast.Abstract;
import com.starview.star.compiler.ast.Apply;
import com.starview.star.compiler.ast.IAbstract;
import com.starview.star.compiler.util.PrettyPrintDisplay;

@SuppressWarnings("serial")
public class FmtApplyApplyPtn implements FmtPtnOp
{
  private final FmtPtnOp opOp;
  private final FmtPtnOp argOp;

  public FmtApplyApplyPtn(FmtPtnOp opOp, FmtPtnOp argOp)
  {
    this.opOp = opOp;
    this.argOp = argOp;
  }

  @Override
  public formatCode apply(IAbstract term, IAbstract env[], Location loc)
  {
    if (term instanceof Apply) {
      Apply apply = (Apply) term;

      formatCode mode = opOp.apply(apply.getOperator(), env, loc);

      if (mode == formatCode.applies) {
        IArray args = apply.getArgs();
        IAbstract tpl = Abstract.tupleTerm(loc, args);
        mode = argOp.apply(tpl, env, loc);
      }
      return mode;
    } else
      return formatCode.notApply;
  }

  @Override
  public int getSpecificity()
  {
    return opOp.getSpecificity() + argOp.getSpecificity();
  }

  @Override
  public void prettyPrint(PrettyPrintDisplay disp)
  {
    opOp.prettyPrint(disp);
    disp.append("@");
    argOp.prettyPrint(disp);
  }

  @Override
  public String toString()
  {
    return PrettyPrintDisplay.toString(this);
  }
}
